package com.ts.common.utils;

import com.alibaba.fastjson.JSON;
import com.ts.animal.constant.AnimalConstant;
import com.ts.common.enums.ResultCode;
import com.ts.system.domain.DeptDO;
import com.ts.system.util.SystemUtil;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import javax.servlet.http.HttpServletRequest;
import java.util.Enumeration;
import java.util.Map;
import java.util.TreeMap;

/**
 * @author bobby
 * @version V1.0
 * @Package com.ts.common.utils
 * @date 2022-9-13 15:57
 * @Copyright © 2019-2039 广州天迅网络科技有限公司
 */
public class UtilSignature {

    private static Logger log = LoggerFactory.getLogger(UtilSignature.class);

    /**
     * 参数加密
     *
     * @HttpServletRequest request
     */
    public static Boolean checkSignature(HttpServletRequest request, ResponseResult responseResult) {
        //因为需要排序，直接使用TreeMap
        Map<String, Object> params = new TreeMap<String, Object>();
        //header 信息
        String signature = "signature";
        String appid = "appid";
        String timestamp = "timestamp";
        String headerSignature = request.getHeader(signature);
        String headerAppid = request.getHeader(appid);
        String headerTimestamp = request.getHeader(timestamp);
        if (StringUtils.isAnyEmpty(headerSignature, headerAppid, headerTimestamp)) {
            log.info("接口appid、timestamp、signature为空！");
            responseResult.setCode(ResultCode.FAIL).setMsg("header参数appid、timestamp、signature不可为空");
            return false;
        }
        long currentTimeMillis = System.currentTimeMillis();
        //5分钟内有效
        try {
            String timeoutStr = SystemUtil.getSystemParams().get(AnimalConstant.key_name_open_api_timeout).getParamValue();
            if ((currentTimeMillis / 1000 - Long.valueOf(headerTimestamp)) / 60 > Long.valueOf(timeoutStr)) {
                log.info("时间戳超时,不可用");
                responseResult.setCode(ResultCode.FAIL).setMsg("接口请求已超时，请重新请求");
                return false;
            }
        } catch (Exception e) {
            log.info("时间戳参数格式错误！");
            responseResult.setCode(ResultCode.FAIL).setMsg("header参数timestamp格式错误");
            return false;
        }
        params.put(appid, headerAppid);
        params.put(timestamp, headerTimestamp);
        log.info("header 信息：{}", JSON.toJSONString(params));
        //body 信息
       /* try {
            String dataString = UtilString.getString(request.getInputStream());
            TreeMap<String, Object> bodyData = JSON.parseObject(dataString, TreeMap.class);
            params.putAll(bodyData);
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
        log.info("header+body 信息：{}", JSON.toJSONString(params));*/
        //Param
        Enumeration enu = request.getParameterNames();
        while (enu.hasMoreElements()) {
            String paraName = (String) enu.nextElement();
            params.put(paraName, request.getParameter(paraName));
        }
        log.info("Param 信息：{}", JSON.toJSONString(params));

        //排序拼接
        StringBuffer signStr = new StringBuffer();
        for (String key : params.keySet()) {
            signStr.append(key).append(params.get(key));
        }
        log.info("加密拼接字符串(传入参数)：{}", headerSignature);
        log.info("未加密拼接字符串：{}", signStr.toString());

        DeptDO deptDO = SystemUtil.getAppidDepts().get(headerAppid);
        if (deptDO == null || deptDO.getSecret() == null) {
            responseResult.setCode(ResultCode.FAIL).setMsg("非法参数，请检查header参数appid");
            return false;
        }

        if (deptDO == null || deptDO.getDelFlag() == 0) {
            responseResult.setCode(ResultCode.FAIL).setMsg("secret已到期，请联系管理员");
            return false;
        }

        //https://www.cmd5.com/hash.aspx?s=123456
        String encryptSignStr = MD5Utils.encryptInSalt(signStr.toString(), deptDO.getSecret());
        log.info("密钥secret:[{}],处理后加密拼接字符串：{}", deptDO.getSecret(), encryptSignStr);

        if (encryptSignStr.equals(headerSignature)) {
            return true;
        } else {
            responseResult.setCode(ResultCode.FAIL).setMsg("非法参数，请检查header参数signature");
            return false;
        }
    }

    public static void main(String[] args) {
        Map<String, Object> map = new TreeMap<String, Object>();
        //map.put("appid", "Ssd66Mzn");
        map.put("appid", "BEwTFNog");
        map.put("timestamp", System.currentTimeMillis() / 1000);//
        map.put("startTime", "2023-01-06 11:57:32");
        map.put("endTime", "2023-01-06 13:57:32");
        //排序拼接
        StringBuffer signStr = new StringBuffer();
        for (String key : map.keySet()) {
            signStr.append(key).append(map.get(key));
        }

        System.out.println("未加密串：" + signStr.toString());
        String secret = "0c4e0063c7a941beb8898f9d8a312e9e";
        System.out.println("secret：" + secret);
        String encryptSignStr = MD5Utils.encryptInSalt(signStr.toString(), secret);
        map.put("signature", encryptSignStr);
        System.out.println("处理后加密拼接字符串:" + encryptSignStr);
        System.out.println(JSON.toJSONString(map));
//

//        String encryptSignStr = MD5Utils.encrypt("16e56267ff4a4956b7f575e5b4567729.appidSYNHGD#dc27endTime2022-10-10 12:11:11startTime2022-10-10 10:11:11timestamp1664024419");
//        System.out.println(encryptSignStr);


//        System.out.println(MD5Utils.encryptInSalt("appidSsd66MznendTime2022-09-14 18:00:01startTime2022-09-14 15:00:01timestamp1663148253","16e56267ff4a4956b7f575e5b4567729"));
    }
}
